/***************************************************************************************************
  Copyright(C)   2011-9-5
  All rights reserved.
  File Name: clientservice.h

  Description:配置模块服务端处理块
              每一个服务的所有处理都在这个文件内，接收数据，发送数据等

  ***************************************************************************************************/

#ifndef CLIENTSERVICE_H
#define CLIENTSERVICE_H


#include <errno.h>
#include <QDir>
#include <QTcpSocket>
#include <QFileInfoList>
#include <QLabel>


#include "public/environment.h"
#include "public/configclass.h"
#include "public/recepkgmanage.h"
#include "log.h"


typedef struct LOSTPKG{
    QString fileName;
    QMap<int, qint64> lostPkgMap;
}LostPkgStruct;


extern QString g_NotePath;

class ClientService : public QTcpSocket
{
    Q_OBJECT
    LOG4QT_DECLARE_QCLASS_LOGGER

public:
    ClientService(int socketId, int state = 0, QObject *parent = 0);
    ~ClientService();

    void init();
    void writeToFile();
    void readFromFile();


    //发送LCD状态，包括设置LCD状态和当前状态，type = 0为设置LCD状态，type = 1为LCD当前状态
    void sendSetLcdState(const QMap<qint16, qint8>& stateMap, const int type = 0);


private:
    Configclass configclass;
    QFile sendFile;

    int socketDescriptor;

    bool isDataProUnfinish;                 //是否有数据未处理
    bool isEndErr;                          //错误标志，如果出现错误就将错误的数据打印到一个文件上
    bool isWantEnvirBright;                 //是否想要环境光度
    bool isUpdateSer;
    bool isPause;                           //是否暂停下载
    bool isClientClose;                     //客户端是否即将关闭
    bool isCheckLcdMode;                    //是否正在开启测试LCD模式


    QList<ReceInfoStruct> receInfoList;     //接收文件信息列表
    int receInfoNum;

    QByteArray halfBytes;                   //包被切开时，不完整的数据将存贮在这，等待收到下一次
                                            //数据时再整合成一个完整的数据包

    int serviceState;                       //服务端状态，0：第一次运行 1：更新成功 2，更新失败
    QTimer readTimer;

private:
    inline qint64 writeBytes(const QByteArray &data);

    void sendConnReply();                                           //连接后发送连接成功回复
//    void sendUpateState(int state);                               //发送此服务状态

    void sendConfigData(qint8 cmd, const qint8 state);          //发送配置数据
    bool sendFileData(char *fileName, const qint64 pos = 0);       //发送文件

    void sendUnfinishFile(const QString& fileName, const QList<FilePkgStruct> unSendPkgList);

    //发送文件列表
    void sendFileInfoList(const qint32 startDate, const qint32 endDate);

    void sendLcdIDList();

    void sendErrInfo(qint8 type, ERRENUM error, const QString& fileName = 0);    //发送错误信息

    //分析配置信息数据
    void analysisConfigData(const QByteArray& receData);

    void changeLocalDateTime(const QByteArray& receData);

    //分析日记文件请求列表
    void analysisNoteFileInfoData(const QByteArray& receData);

    //分析文件数据
    bool analysisFileData(QByteArray &receBytes);

    void analysisUnfinishPkg(QByteArray &receData);

    void analysisLcdCmd(const QByteArray& receData);

    //分析测试LCD屏的数据
    void analysisChcekLcdData(const QByteArray& receData);

    //分析喂狗数据
    void analysisFeedData(const QByteArray &receData);

    //分析更新服务器数据
    void analysisupdateSerData(const QByteArray &receData);

    //分析客户端检查连接状态发送来的数据
    void analysisCheckConnectDate(const QByteArray &receData);

    //下载文件完成
    void downLoadFinish(const QByteArray& receData);

    //处理收到的数据
    void processReceData(const QByteArray& receData);



signals:
    void error(QTcpSocket::SocketError socketError);                        //连接发生错误信号
    void disconnectSignal();                                                //断开信号
    void downLoadProgress(const QString &fileName, const int progress);     //下载进度信号
    void receFeedData(const FreedDogStruct freedDogStruct);                 //收到喂狗数据信号


    void serviceInfoSignal(const QString& fileName, const int fileLen);     //发送更新服务器信息

    //发送接收更新文件情况 0：开始更新 1：更新成功 -1:更新失敗
    void updateService(const int state, const int fileCount);

    void fileDownloadFinish(const QString fileName);                        //文件接收完成信号
    void downLoadErr(const QString& fileName, const ERRENUM enumErr);               //下载出错信号

//    void receSetLcdTraValueCmd(const double lcdK, const int transformValue);
    void changeBriLv(const LcdSettingStruct& settingStruct);            //收到改变LCD 亮度等级信息

    void receSetLcdIDListCmd(const QMap<qint16, qint8>& lcdState);

//    void receSetLcdSettingsCmd(const LcdSettingStruct& lcdSettings);
    void changeLcdBright(const qint16 brightness, const QList<quint16>& panelIDList);

    void getLcdStatus();
    void getLcdSetting();

    void receLcdBackLightCtl(const qint8 cmd, const QList<quint16>& panelIDList);
    void receQueryVideoStatus(const qint16 cmd);

    void receSlcdCollectState(const QList<PanelInfoStruct>& infoList);
//    void sendDebugMsg(const QString& msg);

    void updateConfig();
    void restoreDefaultConfig();                              //恢复默认配置

    void checkLcdCmd(const qint8 cmd);

private slots:
    void receDataFromClient();                                //从客户端收到的数据
    void dispSocketError(QAbstractSocket::SocketError);       //显示连接错误
    void disConnectSlot();                                    //断开插槽

    void sendEnvirBrightness(const qint16 brightness);

    void sendSetLcdTraValueStatus(const qint8 state);
    void sendSetLcdSettingStatus(const qint8 state);
    void sendLcdSetting(const LcdSettingStruct& lcdSettings);
    void sendVideoStatus(const QList<LCDSTATUS>& statusList, const bool isSendToTis);

    void sendServiceClose();
    void sendSystemState(const SystemState& state);


    //lcd回复状态,包括亮度设置和背景灯设置这２个设置
    void sendLcdAnswerStatus(QList<LCDSTATUS> status);

//    void deleteService();

};

#endif // CLIENTSERVICE_H
